﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Routing;
using System.Web.Mvc;

namespace ASPItalia.ModelVirtualCasting.Web.Utils
{
	/// <summary>
	/// Si assicura che le route di MVC finiscano con lo slash finale. Utile per le tecniche SEO.
	/// </summary>
	public class SEOUrlRoute : Route
	{
		public SEOUrlRoute(string url, IRouteHandler routeHandler)
			: base(url, routeHandler) { }
		public SEOUrlRoute(string url, RouteValueDictionary defaults, IRouteHandler routeHandler)
			: base(url, defaults, routeHandler) { }
		public SEOUrlRoute(string url, RouteValueDictionary defaults, RouteValueDictionary constraints, IRouteHandler routeHandler)
			: base(url, defaults, constraints, routeHandler) { }
		public SEOUrlRoute(string url, RouteValueDictionary defaults, RouteValueDictionary constraints, RouteValueDictionary dataTokens, IRouteHandler routeHandler)
			: base(url, defaults, constraints, dataTokens, routeHandler) { }

		public override VirtualPathData GetVirtualPath(RequestContext requestContext, RouteValueDictionary values)
		{
			VirtualPathData path = base.GetVirtualPath(requestContext, values);

            if (path != null)
            {
                int indexOfQueryString = path.VirtualPath.IndexOf("?");
                if (indexOfQueryString != -1)
                {
                    path.VirtualPath = string.Concat(
                        path.VirtualPath.Substring(0, indexOfQueryString),
                        "/",
                        path.VirtualPath.Substring(indexOfQueryString));
                }
                else
                {
                    path.VirtualPath = string.Concat(path.VirtualPath, 
						string.IsNullOrEmpty(path.VirtualPath)?string.Empty: "/" );
                }
            }
			return path;
		}
	}

	public static class RouteExtensions
	{
		/// <summary>
		/// Mappa una route con lo slash finale.
		/// </summary>
		/// <param name="routes"></param>
		/// <param name="name"></param>
		/// <param name="url"></param>
		/// <param name="defaults"></param>
		public static void MapSEORoute(this RouteCollection routes, string name, string url, object defaults)
		{
			routes.MapSEORoute(name, url, defaults, null);
		}

		/// <summary>
		/// Mappa una route con lo slash finale.
		/// </summary>
		/// <param name="routes"></param>
		/// <param name="name"></param>
		/// <param name="url"></param>
		/// <param name="defaults"></param>
		public static void MapSEORoute(this RouteCollection routes, string name, string url, object defaults, object constraints)
		{
			if (routes == null)
				throw new ArgumentNullException("routes");

			if (url == null)
				throw new ArgumentNullException("url");

			var route = new SEOUrlRoute(url, new MvcRouteHandler())
			{
				Defaults = new RouteValueDictionary(defaults),
				Constraints = new RouteValueDictionary(constraints)
			};

			if (String.IsNullOrEmpty(name))
				routes.Add(route);
			else
				routes.Add(name, route);
		}
	}
}